Release 10.1A: OpenEdge Development:
ProDataSets
Sample procedure: creating a dynamic ProDataSet
Let’s create a simple example to see how these dynamic statements work together. Create a new procedure called
DynamicDataSet.p. This procedure:The ProDataSet can have any number of buffers, but (for the sake of simplicity) creates a single Data-Relation between the top two buffers. Any additional buffers are considered independent buffers not related to others in the ProDataSet.
Here are the parameters for the procedure:
The parameters provide this information:
pcBuffers— A list of buffer handles expressed as a comma-delimited string for temp-tables in the caller to be included in the ProDataSet.pcFields— A list of fields to define the relation between the first two buffers passed in.pcSources— A list of database table names to use as Data-Sources for the buffers, one for each buffer.pcSourceKeys— A list of key fields for the Data-Source tables, one for each Data-Source.pcKeyValue— A key value for the top-level table to use to fill the ProDataSet.phDataSet— The procedure returns the dynamic ProDataSet as anOUTPUTparameter using theDATASET-HANDLEform, so that the caller can inspect and use the ProDataSet.It this first example, the ProDataSet is actually constructed from static temp-tables defined in the calling procedure, so it will work only within a single session. Later you will take advantage of additional dynamic ProDataSet methods and attributes to separate the caller from the called program entirely.
You need these local variables in the procedure:
The first executable statement in the procedure creates a dynamic ProDataSet.
The procedure then walks through the list of temp-table buffer handles passed into it as a comma-separated string and adds each in turn to the ProDataSet, by converting each string back into a handle and executing the
ADD-BUFFERmethod for it:
Next, the procedure adds a single Data-Relation to the ProDataSet, using the first buffer as the parent and the second buffer handle as the child. The
GET-BUFFER-HANDLEmethod returns the ProDataSet’s temp-table buffers in the same order in which they were added. ThepcFieldsparameter defines the parent and child fields to use to establish the relation:
Next, the procedure walks through the list of source tables for the ProDataSet. For each one, it creates a dynamic Data-Source. It then creates a dynamic buffer for the table and uses
ADD-SOURCE-BUFFERto add it to the dynamic Data-Source.The final statement of this group uses a sequence of handle attributes to do several steps. Once again
GET-BUFFER-HANDLEreturns the handle of the temp-table buffer in the ProDataSet that corresponds to the Data-Source. The statement then uses this handle to attach the Data-Source to that buffer:
There’s no problem with using the same buffer handle for each dynamic buffer and the same handle for each dynamic Data-Source because as each is added to the ProDataSet, the dynamic ProDataSet can keep track of them internally. Attributes and methods such as
GET-BUFFER-HANDLElet you walk through the ProDataSet after it’s been built so that you can identify all of its components.Now the procedure needs to prepare a database query for the table that is the source for the first, top-level temp-table in the ProDataSet so that the ProDataSet can be filled with all the records related to a single top-level record.
For this entry, the procedure creates a dynamic query and adds the dynamic buffer for this table’s database source table as the query’s buffer. Then it constructs a
QUERY-PREPAREstring from the table name, the key field for the table, and the key value to use to populate the ProDataSet. (Note that for simplicity the procedure expects only one key field for each Data-Source.) Finally, it makes this dynamic query the query for the first Data-Source:
This ends the loop that walks through the list of Data-Sources.
Finally, the procedure issues a FILL on the ProDataSet handle, and cleans up by deleting the dynamic query and each dynamic Data-Source:
After this method executes, the procedure returns the dynamic ProDataSet to the caller as an output parameter.
Now it’s time to write a procedure,
DynamicMain.p, that calls this one. This version of the procedure defines some static temp-tables for the ProDataSet to use, along with a handle to hold the ProDataSet that is returned to it. For example:
Here is the statement that runs the
DynamicDataSetprocedure:
In this statement:
- The first parameter is a list of the buffer handles of this procedure’s static temp-tables. Once again, this simplifies the example to the extent that these handles could, of course, not be passed across an AppServer call to be used on the server. Later in this chapter, you will see a fully dynamic version.
- The second parameter is a list of key fields for the parent and child of the ProDataSet’s one Data-Relation.
- The third parameter is a list of the database source tables.
- The fourth parameter is a list of the (single) key fields for each of those tables.
- The fifth parameter is the key value to use to the top-level table, in this case
Customernumber 1.The final
OUTPUTparameter receives the ProDataSet back from the other procedure.Following this, a series of simple
FOR EACHstatements shows what we get back:
And finally, remember to delete the dynamic ProDataSet that’s been returned:
Design tip: When your procedure creates a dynamic ProDataSet or receives a dynamic ProDataSet as an
OUTPUTparameter, you must remember to take responsibility for deleting it when you are done using it. If you specifyBY-REFERENCEin the parameter, your procedure might not know for sure whether it “owns” the ProDataSet or not. If the called procedure is run locally, then the calling procedure is actually using the ProDataSet owned by the called procedure. If the same procedure is run across an AppServer connection, then the ProDataSet is copied across the network and a new dynamic ProDataSet is created in the calling procedure. In such a case, you should use the statementDELETE OBJECTdataset-handle NO-ERRORto delete the object if it is created for the calling procedure and not otherwise. Progress prevents the calling procedure from deleting a ProDataSet passedBY-REFERENCEfrom another local procedure, and theNO-ERRORkeyword suppresses the warning error in this case.Run the main procedure to see what you get back. First is the single
Customerrecord that satisfies the top-level query, as shown:
![]()
Next come all of its
Orders(this screen shot is somewhat abbreviated):
![]()
These are identified by Progress based on the dynamic Data-Relation between these two tables. Progress has constructed a query automatically that selected just these
Ordersfor the ProDataSet.Last come the
SalesReps. Because there is no Data-Relation defined for this table, and no query for it either, Progress retrieves all theSalesRepsand loads them all into the ProDataSet, as shown:
![]()
|
Copyright © 2005 Progress Software Corporation www.progress.com Voice: (781) 280-4000 Fax: (781) 280-4095 |